package com.seeyon.apps.zjzd.action;

import com.seeyon.apps.zjzd.Kit.FileUtilKit;
import com.seeyon.apps.zjzd.Kit.HttpKit;
import com.seeyon.apps.zjzd.Kit.StrKit;
import com.seeyon.cap4.form.bean.*;
import com.seeyon.cap4.form.modules.engin.trigger.FormTriggerCustomBaseAction;
import com.seeyon.cap4.form.modules.engin.trigger.TriggerActionContext;
import com.seeyon.cap4.form.service.CAP4FormManager;
import com.seeyon.cap4.template.manager.CAPDataListSqlHelpManager;
import com.seeyon.ctp.common.AppContext;
import com.seeyon.ctp.common.SystemEnvironment;
import com.seeyon.ctp.common.constants.ApplicationCategoryEnum;
import com.seeyon.ctp.common.exceptions.BusinessException;
import com.seeyon.ctp.common.file.model.CtpFile;
import com.seeyon.ctp.common.filemanager.dao.AttachmentDAO;
import com.seeyon.ctp.common.filemanager.manager.AttachmentManager;
import com.seeyon.ctp.common.filemanager.manager.FileManager;
import com.seeyon.ctp.common.formula.FormulaUtil;
import com.seeyon.ctp.common.log.CtpLogFactory;
import com.seeyon.ctp.common.po.filemanager.Attachment;
import com.seeyon.ctp.common.po.filemanager.V3XFile;
import com.seeyon.ctp.organization.manager.OrgManager;
import com.seeyon.ctp.util.UUIDLong;
import org.apache.commons.logging.Log;

import java.io.File;
import java.net.URLEncoder;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 签证附件上传回写触发动作类
 */
public class FileUploadFormTriggerCustomAction extends FormTriggerCustomBaseAction {

    private static final Log log = CtpLogFactory.getLog(FileUploadFormTriggerCustomAction.class);

    private OrgManager orgManager = (OrgManager) AppContext.getBean("orgManager");
    private FileManager fileManager = (FileManager) AppContext.getBean("fileManager");
    private AttachmentDAO attachmentDAO = (AttachmentDAO) AppContext.getBean("attachmentDAO");
    private AttachmentManager attachmentManager = (AttachmentManager) AppContext.getBean("attachmentManager");
    private CAP4FormManager cap4FormManager = (CAP4FormManager) AppContext.getBean("cap4FormManager");
    private CAPDataListSqlHelpManager capDataListSqlHelpManager = (CAPDataListSqlHelpManager) AppContext.getBean("capDataListSqlHelpManager");

    @Override
    public String getId() {
        return "3679636878247316127";
    }

    @Override
    public void init() {

    }

    /**
     * 执行特定的触发动作，主要用于处理签证管理档案数据的更新
     * 该方法从表单数据中提取ID卡、签证、照片、护照等字段信息，如存在，则下载附件并上传文件
     *
     * @param triggerActionContext 触发动作上下文，包含表单主豆和启动成员ID等必要信息
     * @throws BusinessException 当执行业务逻辑遇到错误时抛出
     */
    @Override
    public void execute(TriggerActionContext triggerActionContext) throws BusinessException {
        try {
            // 获取表单主表对象
            FormDataMasterBean formDataMasterBean = triggerActionContext.getMasterBean();
            String dataId = StrKit.str(formDataMasterBean.getId());
            // 处理ID卡字段
            String idCardId = StrKit.str(formDataMasterBean.getFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay("ID卡").getName()));
            if (!"".equals(idCardId)) {
                // 获取登录名
                String loginName = orgManager.getMemberById(formDataMasterBean.getStartMemberId()).getLoginName();
                // 下载附件并上传文件
                String displayName = dataId + "_ID卡";
                log.info("displayName:" + displayName);
                attachmentDownload(idCardId, loginName, displayName);
                fileUpload(loginName, displayName);
            }

            // 处理签证字段
            String visa = StrKit.str(formDataMasterBean.getFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay("签证").getName()));
            if (!"".equals(visa)) {
                // 获取登录名
                String loginName = orgManager.getMemberById(formDataMasterBean.getStartMemberId()).getLoginName();
                // 下载附件并上传文件
                String displayName = dataId + "_签证";
                log.info("displayName:" + displayName);
                attachmentDownload(visa, loginName, displayName);
                fileUpload(loginName, displayName);
            }

            // 处理照片字段
            String picture = StrKit.str(formDataMasterBean.getFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay("照片").getName()));
            if (!"".equals(picture)) {
                // 获取登录名
                String loginName = orgManager.getMemberById(formDataMasterBean.getStartMemberId()).getLoginName();
                // 下载附件并上传文件
                String displayName = dataId + "_照片";
                log.info("displayName:" + displayName);
                attachmentDownload(picture, loginName, dataId + "_照片");
                fileUpload(loginName, displayName);
            }

            // 处理护照字段
            String passport = StrKit.str(formDataMasterBean.getFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay("护照").getName()));
            if (!"".equals(passport)) {
                // 获取登录名
                String loginName = orgManager.getMemberById(formDataMasterBean.getStartMemberId()).getLoginName();
                // 下载附件并上传文件
                String displayName = dataId + "_护照";
                log.info("displayName:" + displayName);
                attachmentDownload(passport, loginName, displayName);
                fileUpload(loginName, displayName);
            }

            // 处理综合附件字段
            String comprehensive_attachment = StrKit.str(formDataMasterBean.getFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay("综合附件").getName()));
            if (!"".equals(comprehensive_attachment)) {
                // 获取登录名
                String loginName = orgManager.getMemberById(formDataMasterBean.getStartMemberId()).getLoginName();
                // 下载附件并上传文件
                String displayName = dataId + "_综合";
                log.info("displayName:" + displayName);
                attachmentDownload(comprehensive_attachment, loginName, displayName);
                fileUpload(loginName, displayName);
            }
        } catch (Exception e) {
            // 日志记录错误
            log.error("更新签证管理档案数据失败:", e);
        }
    }

    /**
     * 根据身份证ID和登录名下载附件
     * 本方法从系统中获取附件信息，并通过HTTP请求下载附件文件
     * 下载完成后，将文件解压（如果需要），并删除原始下载文件
     *
     * @param idCardId  身份证ID，用于查询附件
     * @param loginName 用户登录名，用于获取下载附件的权限
     * @throws BusinessException 当附件下载过程中发生错误时抛出
     */
    private void attachmentDownload(String idCardId, String loginName, String folderName) throws BusinessException {
        try {
            // 根据身份证ID获取附件文件ID列表
            List<Long> fileIdList = attachmentManager.getBySubReference(Long.parseLong(idCardId));
            // 获取基础URL
            String url = StrKit.str(FormulaUtil.getVar("url"));
            // 构造获取token的URL
            String tokenUrl = url + "/seeyon/rest/token";
            // 获取token ID
            String tokenId = HttpKit.getToken(loginName, tokenUrl);
            if (!fileIdList.isEmpty()) {
                for (Long fileId : fileIdList) {
                    // 根据文件ID获取文件信息
                    V3XFile v3XFile = fileManager.getV3XFile(fileId);
                    // 构造附件下载URL
                    String attUrl = url + "/seeyon/rest/attachment/file/" + v3XFile.getId() + "?fileName=" + URLEncoder.encode(v3XFile.getFilename(), "UTF-8") + "&token=" + tokenId + "";
                    // 下载附件文件
                    File file = HttpKit.downloadFile(attUrl, new HashMap<String, Object>(), folderName, v3XFile.getFilename());
                    String path = file.getPath();
                    // 如果文件是压缩文件，解压文件
                    String path_new = path + "\\" + v3XFile.getFilename();
                    FileUtilKit.unRarZip7Z(path_new, folderName);
                    // 删除已下载的文件
                    FileUtilKit.deleteFiles(new File(path));
                }
            }
        } catch (Exception e) {
            // 记录附件下载失败的日志
            log.error("附件下载失败:", e);
        }
    }

    /**
     * 文件上传方法
     *
     * @param loginName    用户登录名称，用于获取访问令牌
     * @param fieldDisplay 表单字段显示名称，用于关联附件信息
     *                     <p>
     *                     此方法负责从指定路径读取文件，并上传到目标系统中
     *                     它首先根据表单代码获取表单信息，然后构造上传文件的URL，
     *                     通过用户登录名获取令牌，最后遍历本地文件，逐个上传
     */
    private void fileUpload(String loginName, String fieldDisplay) throws BusinessException {
        try {
            // 根据表单代码获取表单信息
            FormBean formBean = cap4FormManager.getFormByFormCode("QZXXB_001");

            // 获取基础文件夹路径并确保路径使用正斜杠分隔
            String systemUrl = SystemEnvironment.getBaseFolder().replaceAll("\\\\", "/");

            // 定义上传文件夹路径
            String pathUrl = systemUrl + "/upload/customFile/upload/" + fieldDisplay + "/";
            File file = new File(pathUrl);

            // 获取目标系统的基础URL和令牌URL
            String url = StrKit.str(FormulaUtil.getVar("url"));
            String tokenUrl = url + "/seeyon/rest/token";

            // 获取上传附件的URL
            String fileUrl = url + "/seeyon/rest/attachment?token=" + HttpKit.getToken(loginName, tokenUrl);

            // 如果文件夹存在且为目录，则进一步处理
            if (file.exists() && file.isDirectory()) {
                File[] files = file.listFiles();
                if (files != null) {
                    for (File file_tmp : files) {
                        // 处理文件名，获取新的文件名用于后续操作
                        String fileName = file_tmp.getName();
                        String fileName_new = "";
                        if (fileName.contains("_")) {
                            fileName_new = fileName.split("_")[0];
                        } else {
                            fileName_new = fileName.split("\\.")[0];
                        }
                        String fieldDisplay_new = "";
                        if (fieldDisplay.contains("综合")) {
                            if (fileName.contains("_")) {
                                String fieldNameStr = fileName.split("_")[1];
                                if (fieldNameStr.contains(".")) {
                                    fieldDisplay_new = fieldNameStr.split("\\.")[0];
                                } else {
                                    fieldDisplay_new = fieldNameStr;
                                }
                            } else {
                                fieldDisplay_new = fileName.split("\\.")[0];
                            }
                            if (fieldDisplay_new.equals("ID")) {
                                fieldDisplay_new = "ID卡";
                            } else if (fieldDisplay_new.equals("VISA")) {
                                fieldDisplay_new = "签证";
                            } else if (fieldDisplay_new.equals("PHOTO")) {
                                fieldDisplay_new = "照片";
                            } else if (fieldDisplay_new.equals("PASSPORT")) {
                                fieldDisplay_new = "护照";
                            }
                        } else {
                            if (fieldDisplay.contains("_")) {
                                fieldDisplay_new = fieldDisplay.split("_")[1];
                            }
                        }

                        log.info("fieldDisplay_new:" + fieldDisplay_new);
                        // 根据文件名获取表单数据主键对象
                        FormDataMasterBean formDataMasterBean = getFormDataMasterBean(fileName_new, fieldDisplay_new);
                        if (formDataMasterBean != null) {
                            // 上传文件并处理返回结果
//                            String fileResult = HttpKit.uploadFile(fileUrl, file_tmp);
                            CtpFile ctpFile = new CtpFile(file_tmp.getPath());
                            if (!ctpFile.exists()) {
                                log.error("文件不存在:" + file_tmp.getPath());
                                return;
                            }
                            V3XFile v3xFile = fileManager.save(ctpFile, ApplicationCategoryEnum.cap4Form, fileName, new Date(), true);
                            if (v3xFile != null) {
                                // 获取文件URL并创建附件对象，保存到数据库
//                                String fileUrl_oa = StrKit.getFileUrl(fileResult);
//                                V3XFile v3xFile = fileManager.getV3XFile(Long.parseLong(fileUrl_oa));
                                Attachment attachment = new Attachment();
                                attachment.setIdIfNew();
                                attachment.setCategory(v3xFile.getCategory());
                                attachment.setCreatedate(v3xFile.getCreateDate());
                                attachment.setDescription(v3xFile.getDescription());
                                attachment.setFilename(v3xFile.getFilename());
                                attachment.setFileUrl(v3xFile.getId());
                                attachment.setReference(formDataMasterBean.getId());
                                Long sub_reference = UUIDLong.longUUID();
                                attachment.setSubReference(sub_reference);
                                attachment.setSort(1);
                                attachment.setType(v3xFile.getType());
                                attachment.setMimeType(v3xFile.getMimeType());
                                attachment.setSize(v3xFile.getSize());
                                attachmentDAO.save(attachment);
                                // 更新表单数据主键对象的字段值，并保存表单数据
                                formDataMasterBean.addFieldValue(formDataMasterBean.getFormTable().getFieldBeanByDisplay(fieldDisplay_new).getName(), sub_reference);
                                cap4FormManager.saveOrUpdateFormData(formDataMasterBean, formBean.getId(), true, null);
                            }
                        }
                    }

                }
            }
            log.info("根据工号上传人员附件信息成功");
            // 删除已上传的文件
            FileUtilKit.deleteFiles(new File(pathUrl));
        } catch (Exception e) {
            log.error("附件上传失败:", e);
        }
    }

    /**
     * 根据人员编码和字段显示名称获取表单数据主表
     *
     * @param memberCode   人员编码，用于查询表单数据
     * @param fieldDisplay 字段显示名称，用于确定查询的字段
     * @return FormDataMasterBean 表单数据主豆，如果找不到则返回null
     * @throws BusinessException 当获取表单数据失败时抛出的业务异常
     */
    private FormDataMasterBean getFormDataMasterBean(String memberCode, String fieldDisplay) throws BusinessException {
        FormDataMasterBean formDataMasterBean = null;
        try {
            // 根据表单代码获取表单对象
            FormBean formBean = cap4FormManager.getFormByFormCode("QZXXB_001");
            // 获取主表的表名
            String tableName = formBean.getMasterTableBean().getTableName();
            // 根据字段显示名称获取字段名
            log.info("根据字段显示名称获取字段名:" + fieldDisplay);
            String fieldName = formBean.getFieldBeanByDisplay(fieldDisplay).getName();
            // 获取员工号字段名
            String ygh_fieldName = formBean.getFieldBeanByDisplay("员工号").getName();
            // 构建SQL查询语句
            StringBuilder sql = new StringBuilder();
            sql.append("select id,").append(fieldName).append(" from ").append(tableName);
            sql.append(" where ").append(ygh_fieldName).append(" = '").append(memberCode).append("'");
            // 执行SQL查询获取数据列表
            List dataList = capDataListSqlHelpManager.selectDataList(sql.toString(), null);
            // 检查查询结果是否为空
            if (!dataList.isEmpty()) {
                // 获取第一行数据并转换为Map
                Map<String, Object> dataMap = (Map<String, Object>) dataList.get(0);
                // 获取数据ID
                String dataId = StrKit.str(dataMap.get("id"));
                // 根据数据ID获取表单数据主豆
                formDataMasterBean = cap4FormManager.getDataMasterBeanById(Long.parseLong(dataId), formBean, null);
            } else {
                // 如果数据为空，则记录日志并返回null
                log.info("劳工号[" + memberCode + "]在档案表中未匹配到相关信息!");
            }
        } catch (Exception e) {
            // 捕获异常并记录错误日志
            log.error("获取表单数据失败:", e);
        }
        // 返回表单数据主对象
        return formDataMasterBean;
    }


}
